-module(poly).
-export([normal/1,
         nnormal/1,
         find_min_max_from_triangles/1]).

%% @spec normal(Triangulo::triangle()) -> Normal::vec3()
%% @doc Calcula la normal de un triangulo
normal({A = {vec3, _, _, _}, B = {vec3, _, _, _}, C = {vec3, _, _, _}}) ->
    U = vector:rest(B, A),
    V = vector:rest(C, A),
    vector:cross(U, V).

%% @spec nnormal(Triangulo::triangle()) -> NormalNormalizada::vec3()
%% @doc Calcula la normal "normalizada" de un triangulo
nnormal(P = {{vec3, _, _, _}, {vec3, _, _, _}, {vec3, _, _, _}}) ->
    vector:normalize(normal(P)).

%% @spec find_min_max_from_triangles(Triangulos::triangleList()) -> Rango::vec3Range()
%% @doc Encuentra el valor minimo y maximo para X, Y y Z
find_min_max_from_triangles(Tris) ->
    find_min_max_from_triangles({{vec3, 0, 0, 0}, {vec3, 0, 0, 0}}, Tris).

find_min_max_from_triangles(MinMax, []) ->
    MinMax;
find_min_max_from_triangles({{vec3, Xmin, Ymin, Zmin}, {vec3, Xmax, Ymax, Zmax}}, [ {{{vec3, X1, Y1, Z1}, {vec3, X2, Y2, Z2}, {vec3, X3, Y3, Z3}}, _} | T ]) ->
    {NXmin, NXmax} = util:find_min_max([Xmin, Xmax, X1, X2, X3]),
    {NYmin, NYmax} = util:find_min_max([Ymin, Ymax, Y1, Y2, Y3]),
    {NZmin, NZmax} = util:find_min_max([Zmin, Zmax, Z1, Z2, Z3]),
    find_min_max_from_triangles({{vec3, NXmin, NYmin, NZmin}, {vec3, NXmax, NYmax, NZmax}}, T).
